﻿using B.Z.BasicData.API.Read.DTO;
using B.Z.BasicData.Domain.Entity.Authorize;
using B.Z.BasicData.ErrorCode;
using B.Z.BasicData.Infrastructure;
using MediatR;
using Microsoft.EntityFrameworkCore;
using System.Collections.Generic;
using System.Security.Cryptography;

namespace B.Z.BasicData.API.Read.Application.Menu
{
    public class MenuQueryCommandHandler : IRequestHandler<MenuQueryCommand, APIResult<APIPaging<MenuDto>>>
    {
        private readonly IBaseRepository<T_Menu> menuRepository;

        public MenuQueryCommandHandler(IBaseRepository<T_Menu> menuRepository)
        {
            this.menuRepository = menuRepository;
        }

        public Task<APIResult<APIPaging<MenuDto>>> Handle(MenuQueryCommand request, CancellationToken cancellationToken)
        {
            APIResult<APIPaging<MenuDto>> result = new APIResult<APIPaging<MenuDto>>();
            result.Code = APIEnum.ok;
            result.Message = "获取成功";
           
            APIPaging<MenuDto> paging = new APIPaging<MenuDto>();
            List<MenuDto> menus = GetList(0);
            paging.RecordCount = menus.Count();
            paging.List = menus.OrderByDescending(x => x.OrderbyDesc).Skip((request.PageIndex - 1) * request.PageSize).Take(request.PageSize).ToList();
            result.Data = paging;
            return Task.FromResult(result);
        }


        public List<MenuDto> GetList(int pid) 
        {
            //List<MenuDto> dtos = new List<MenuDto>();
            //var alist = menuRepository.GetAll().AsNoTracking().Where(x=>x.Pid==pid);
            //var list = (from a in alist
            //           join b in alist
            //           on a.Pid equals b.Id into T1
            //           from b in T1.DefaultIfEmpty()
            //           select new MenuDto
            //           {
            //               MenuName = a.MenuName,
            //               Url = a.Url,
            //               Pid = a.Pid,
            //               OrderbyDesc = a.OrderbyDesc,
            //               ParentMenuName = b.MenuName,
            //               Id = a.Id,
            //               CreateUserName = a.CreateUserName,
            //               CreateTime = a.CreateTime,
            //               UpdateUserName = a.UpdateUserName,
            //               UpdateTime = a.UpdateTime,
            //           }).ToList();
            //foreach (var item in list)
            //{
            //    MenuDto dto = new MenuDto()
            //    {
            //        MenuName = item.MenuName,
            //        Url = item.Url,
            //        Pid = item.Pid,
            //        OrderbyDesc = item.OrderbyDesc,
            //        ParentMenuName = item.ParentMenuName,
            //        Id = item.Id,
            //        CreateUserName = item.CreateUserName,
            //        CreateTime = item.CreateTime,
            //        UpdateUserName = item.UpdateUserName,
            //        UpdateTime = item.UpdateTime,
            //        Children = GetList(item.Id)
            //    };
            //    dtos.Add(dto);
            //}
            //return dtos;

            // 获取当前层级的菜单列表
            var menuEntities = menuRepository.GetAll()
                .AsNoTracking()
                .Where(x => x.Pid == pid)
                .ToList();

            // 提取当前层级所有菜单的ID，用于后续查询父菜单
            var menuIds = menuEntities.Select(x => x.Pid).ToList();

            // 一次性查询所有父菜单信息，避免N+1问题
            var parentMenus = menuRepository.GetAll()
                .AsNoTracking()
                .Where(x => menuIds.Contains(x.Id))
                .ToDictionary(x => x.Id, x => x.MenuName);

            // 转换实体为DTO并递归获取子菜单
            var dtos = menuEntities.Select(menu => new MenuDto
            {
                MenuName = menu.MenuName,
                Url = menu.Url,
                Pid = menu.Pid,
                OrderbyDesc = menu.OrderbyDesc,
                // 从字典中获取父菜单名称，不存在则为null
                ParentMenuName = parentMenus.GetValueOrDefault(menu.Pid),
                Id = menu.Id,
                CreateUserName = menu.CreateUserName,
                CreateTime = menu.CreateTime,
                UpdateUserName = menu.UpdateUserName,
                UpdateTime = menu.UpdateTime,
                // 递归获取子菜单
                Children = GetList(menu.Id)
            }).ToList();
            return dtos;
        }
    }
}
